package controller

import (
	"database/sql"
	"dsc-server/domain/dto"
	"dsc-server/pkg/model"
	"dsc-server/pkg/service"
	"log"
	"net/http"
	"strconv"

	"github.com/gin-gonic/gin"
	"gorm.io/gorm"
)

// DataSourceController 数据源控制器
type DataSourceController struct {
	BaseController
	DB                *gorm.DB
	DataSourceService *service.DataSourceService
}

// NewDataSourceController 创建DataSourceController实例
func NewDataSourceController(db *gorm.DB) *DataSourceController {
	return &DataSourceController{
		DB:                db,
		DataSourceService: service.NewDataSourceService(db),
	}
}

// Add 添加数据源
func (ctrl *DataSourceController) Add(c *gin.Context) {
	var dataSource model.Datasource
	if err := c.ShouldBind(&dataSource); err != nil {
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "参数绑定失败"))
		return
	}

	result := ctrl.DataSourceService.Add(&dataSource)
	c.JSON(http.StatusOK, result)
}

// GetAll 获取所有数据源
func (ctrl *DataSourceController) GetAll(c *gin.Context) {
	dataSources, err := ctrl.DataSourceService.GetAll()
	if err != nil {
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "获取数据源失败"))
		return
	}

	c.JSON(http.StatusOK, dataSources)
}

// Detail 获取数据源详情
func (ctrl *DataSourceController) Detail(c *gin.Context) {
	idStr := c.Param("id")
	id, err := strconv.ParseUint(idStr, 10, 32)
	if err != nil {
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "ID参数错误"))
		return
	}

	dataSource, err := ctrl.DataSourceService.Detail(uint(id))
	if err != nil {
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "获取详情失败"))
		return
	}

	c.JSON(http.StatusOK, dataSource)
}

// Delete 删除数据源
func (ctrl *DataSourceController) Delete(c *gin.Context) {
	idStr := c.Param("id")
	id, err := strconv.ParseUint(idStr, 10, 32)
	if err != nil {
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "ID参数错误"))
		return
	}

	result := ctrl.DataSourceService.Delete(uint(id))
	c.JSON(http.StatusOK, result)
}

// Update 更新数据源
func (ctrl *DataSourceController) Update(c *gin.Context) {
	var dataSource model.Datasource
	if err := c.ShouldBind(&dataSource); err != nil {
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "参数绑定失败"))
		return
	}

	result := ctrl.DataSourceService.Update(&dataSource)
	c.JSON(http.StatusOK, result)
}

// Connect 测试数据源连接
func (ctrl *DataSourceController) Connect(c *gin.Context) {
	var dataSource model.Datasource
	if err := c.ShouldBind(&dataSource); err != nil {
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "参数绑定失败"))
		return
	}

	// 尝试连接数据库
	var db *sql.DB
	var err error

	switch dataSource.Type {
	case "mysql":
		// 假设URL格式为: host:port/dbname
		db, err = sql.Open("mysql", dataSource.Username+":"+dataSource.Password+"@tcp("+dataSource.Url+")/")
	case "postgres":
		// 假设URL已经是完整的连接字符串
		db, err = sql.Open("postgres", dataSource.Url)
	default:
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "不支持的数据库类型"))
		return
	}

	if err != nil {
		log.Printf("数据库连接失败: %v", err)
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "数据库连接失败: "+err.Error()))
		return
	}
	defer db.Close()

	// 测试连接
	err = db.Ping()
	if err != nil {
		log.Printf("数据库连接测试失败: %v", err)
		c.JSON(http.StatusOK, dto.FailureMessage(nil, "数据库连接测试失败: "+err.Error()))
		return
	}

	c.JSON(http.StatusOK, dto.Success(nil))
}
